package fons.model.ontology.calculation;

import java.util.Set;

import com.google.common.base.Function;
import com.google.common.collect.Sets;

import fons.model.ontology.Dimension;
import fons.util.Pair;

public class BoundConstraint extends AbstractConstraint {
	private final Constraint constraint;
	private final Function<Dimension, Dimension> transformer;
	
	private Variable variable;
	
	public static final Function<Dimension, Dimension> SAME = new Function<Dimension, Dimension>() {
		@Override
		public Dimension apply(Dimension arg0) {
			return arg0;
		}
	};
	
	public static final Function<Dimension, Dimension> PREDECESSOR = new Function<Dimension, Dimension>() {
		@Override
		public Dimension apply(Dimension arg0) {
			return arg0.getPredecessor();
		}
	};
	
	public BoundConstraint (final String name, final Constraint constraint,
			final Function<Dimension, Dimension> transformer) {
		super(name, constraint.getContext());
		this.constraint = constraint;
		this.transformer = transformer;
	}
	
	public BoundConstraint (final Constraint constraint,
			final Function<Dimension, Dimension> transformer) {
		this(constraint.getName(), constraint, transformer);
	}
	
	public Constraint getUnboundConstraint() {
		return this.constraint;
	}
	
	@Override
	@SuppressWarnings("unchecked")
	public Set<Pair<String, Dimension>> getDimensions() {
		return Sets.newHashSet(Pair.<String, Dimension>of(getName(), 
				transformer.apply(this.variable.getDimension(this.constraint.getName()))));
	}
	
	@Override
	public void setUnboundVariable(Variable variable) {
		this.variable = variable;
	}

	@Override
	public String toString() {
		return "BoundConstraint [constraint=" + constraint + ", variable="
				+ variable + "]";
	}
	
	
}
